﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace classbuilder
{
    public partial class Form1 : Form
    {
        private ListViewItem headitem = new ListViewItem("name", 0);

        public Form1()
        {
            InitializeComponent();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            listView1.LargeImageList = imageList1;
            listView1.Items.Add(headitem);

        }
        string head = "#ifndef _{0}_H_\r\n#define _{0}_H_\r\n\r\n{1}\r\n\r\ntypedef struct {{\r\n	void(*Init)(void);\r\n}}{0}Base;\r\n\r\nextern const {0}Base {0};\r\n\r\n#endif\r\n";
        string cfile = "#include \"{0}.h\"\r\nstatic void init(){{\r\n}}\r\n\r\nconst {0}Base {0} = {{\r\n	init,	\r\n}};\r\n";
        string mcuhead = "#ifndef _mcuhead_H_\r\n#define _mcuhead_H_\r\n\r\n#define u8 unsigned char\r\n#define u16 unsigned short\r\n#define u32 unsigned long\r\n\r\n#define s8 signed char\r\n#define s16 signed short\r\n#define s32 signed long\r\n\r\n#define vu8 volatile u8\r\n#define vu16 volatile u16\r\n#define vu32 volatile u32\r\n\r\n\r\n#define BIT0 1\r\n#define BIT1 2\r\n#define BIT2 4\r\n#define BIT3 8\r\n#define BIT4 0x10\r\n#define BIT5 0x20\r\n#define BIT6 0x40\r\n#define BIT7 0x80\r\n#define BIT8 0x100\r\n#define BIT9 0x200\r\n#define BIT10 0x400\r\n#define BIT11 0x800\r\n#define BIT12 0x1000\r\n#define BIT13 0x2000\r\n#define BIT14 0x4000\r\n#define BIT15 0x8000\r\n#define BIT16 0x10000\r\n#define BIT17 0x20000\r\n#define BIT18 0x40000\r\n#define BIT19 0x80000\r\n#define BIT20 0x100000\r\n#define BIT21 0x200000\r\n#define BIT22 0x400000\r\n#define BIT23 0x800000\r\n#define BIT24 0x1000000\r\n#define BIT25 0x2000000\r\n#define BIT26 0x4000000\r\n#define BIT27 0x8000000\r\n#define BIT28 0x10000000\r\n#define BIT29 0x20000000\r\n#define BIT30 0x40000000\r\n#define BIT31 0x80000000\r\n\r\n#define SETBIT(x,y) (x)|=(y)\r\n#define CLRBIT(x,y) (x)&=~(y)\r\n#define CPLBIT(x,y) (x)^=(y);\r\n\r\nunion u2i{{\r\n	vu32 l;\r\n	vu16 li[2];\r\n	vu8 lc[4];\r\n	vu16 i;\r\n	vu8 c[2];\r\n}};\r\n\r\n#define _16T8H(x) (((union u2i*)&x)->c[1])//??16??8?\r\n#define _16T8L(x) (((union u2i*)&x)->c[0])//??16??8?\r\n\r\n#define _32T16H(x) (((union u2i*)&x)->li[1])//??32??16?\r\n#define _32T16L(x) (((union u2i*)&x)->li[0])//??32??16?\r\n\r\n#define _32T8HH(x) (((union u2i*)&x)->lc[3])//??32??8?\r\n#define _32T8H(x) (((union u2i*)&x)->lc[2])//??32???8?\r\n#define _32T8L(x) (((union u2i*)&x)->lc[1])//??32???8?\r\n#define _32T8LL(x) (((union u2i*)&x)->lc[0])//??32?8?\r\n\r\n#define XBIT(x) (((x>>21)&BIT7)|((x>>18)&BIT6)|((x>>15)&BIT5)|((x>>12)&BIT4)|((x>>9)&BIT3)|((x>>6)&BIT2)|((x>>3)&BIT1)|((x)&BIT0))\r\n#define BIN(X) XBIT(0x##X)\r\n\r\n#define BINWORD(b1,b2) ((BIN(b1)<<8)|BIN(b2))\r\n#define BINDWORD(b1,b2,b3,b4) ((BIN(b1)<<24)|(BIN(b2)<<16)|(BIN(b3)<<8)|BIN(b4))\r\n\r\n#define HT4(x,y,z) (((x&(1<<y))!=0)*(z<<2*y))\r\n#define HT16(x,y) (HT4(x,0,y)|HT4(x,1,y)|HT4(x,2,y)|HT4(x,3,y)|HT4(x,4,y)|HT4(x,5,y)|HT4(x,6,y)|HT4(x,7,y))\r\n#define HT32(x,y,v) (~((HT16(x,v)<<16)|(HT16(y,v))))\r\n#define HV32(x,y,v) ((HT16(x,v)<<16)|(HT16(y,v)))\r\n\r\n#define m4(x) *((vu32*)(x))\r\n#define waitTRUE(x,b) while(m4(x)&(b))\r\n#define waitFALSE(x,b) while(!(m4(x)&(b)))\r\n\r\n#endif\r\n";
        string getinfo(string path=null)
        {
            if(path==null)
                path = System.IO.Path.GetTempPath();
            var sw = new StreamWriter(new FileStream(path + headitem.Text + ".h",FileMode.OpenOrCreate));
            sw.Write(string.Format(head, headitem.Text, mcuheadcheck.Checked ? "#include \"mcuhead.h\"\r\n" : "#define u8 unsigned char\r\n#define u16 unsigned short\r\n#define u32 unsigned long\r\n\r\n"));
            sw.Flush();
            sw.Close();

            sw = new StreamWriter(new FileStream(path + headitem.Text + ".c", FileMode.OpenOrCreate));
            sw.Write(string.Format(cfile, headitem.Text));
            sw.Flush();
            sw.Close();

            if(createmcuhead.Checked)
            {
                sw = new StreamWriter(new FileStream(path + "mcuhead.h", FileMode.OpenOrCreate));
                sw.Write(mcuhead);
                sw.Flush();
                sw.Close();
            }



            return path;
        }

        private void listView1_DragDrop(object sender, DragEventArgs e)
        {

        }

        private void listView1_DragEnter(object sender, DragEventArgs e)
        {
            e.Effect = DragDropEffects.Move;
        }

        private void listView1_DragLeave(object sender, EventArgs e)
        {

        }

        private void textBox1_TextChanged(object sender, EventArgs e)
        {
            headitem.Text = textBox1.Text;
        }

        private void listView1_ItemDrag(object sender, ItemDragEventArgs e)
        {
            var path= getinfo();
            string[] files;
            if (createmcuhead.Checked)
                files = new string[3];
            else
                files = new string[2];
            files[0] = path + headitem.Text + ".h";
            files[1] = path + headitem.Text + ".c";
            if (createmcuhead.Checked)
                files[2] = path + "mcuhead.h";
            DoDragDrop(new DataObject(DataFormats.FileDrop, files),DragDropEffects.Move);

        }

        FolderBrowserDialog sf = new FolderBrowserDialog();
        private void 保存ToolStripMenuItem_Click(object sender, EventArgs e)
        {
            
            //sf.Filter = "*.*|(*.*)";
            if (sf.ShowDialog() == DialogResult.OK)
            {
                getinfo(sf.SelectedPath);
            }
        }

        private void mcuheadcheck_CheckedChanged(object sender, EventArgs e)
        {
            createmcuhead.Enabled = mcuheadcheck.Checked;
            if (!mcuheadcheck.Checked)
                createmcuhead.Checked = false;
        }
    }
}
